﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;
using System.ComponentModel;
using System.Data.SqlClient;
using System.Data.OleDb;
using System.Configuration;
using Convert.DBconverter;
using Convert.CPIAMmodel;
using Convert.LOTSmodel;
namespace LOTSConversion
{
    /// <summary>
    /// Interaction logic for MainWindow.xaml
    /// </summary>
    public partial class MainWindow : Window
    {
        public static string CpiamPosMaxRetailStr;
        public static string CpiamPosMaxRetailReceiptsStr;
        public static string LotsConnectionStr;

        public MainWindow()
        {
            InitializeComponent();
            this.DataContext = this;
            //LotsConnectionStr = @"Provider=Microsoft.Jet.OLEDB.4.0;Data Source=D:\LOTS\lots.mdb";//ConfigurationManager.ConnectionStrings["LOTStoCPIAMconvert.Properties.Settings.lotsConnectionString"].ConnectionString; //ConversionConfig.GetFredHQDatabaseConnectionString();
            //CpiamPosMaxRetailStr = ConfigurationManager.ConnectionStrings["LOTStoCPIAMconvert.Properties.Settings.CPIAMPOSMaxRetailConnectionString"].ConnectionString;//ConversionConfig.GetConversionDatabaseConnectionString(); // "Data Source=" + ServerLocation + ";Initial Catalog=" + CpiamPosMaxRetailCatalogue + ";Persist Security Info=True;User ID=dblAdmin;Password=5099223dak;Connect Timeout=0";
            //CpiamPosMaxRetailReceiptsStr = ""; //ConversionConfig.GetConversionDatabaseReceiptsConnectionString(); //"Data Source=" + ServerLocation + ";Initial Catalog=" + CpiamPosMaxRetailReceiptsCatalogue + ";Persist Security Info=True;User ID=dblAdmin;Password=5099223dak;Connect Timeout=0";
            CpiamPosMaxRetailStr = ConversionConfig.GetConversionDatabaseConnectionString();
            CpiamPosMaxRetailReceiptsStr = ConversionConfig.GetConversionDatabaseReceiptsConnectionString();
            DBLabel.Content = "Server: " + ConversionConfig.CONVERSION_DB_SERVER + "  CpiamPosMaxRetail DB: " + ConversionConfig.CONVERSION_DB_NAME + "  CpiamPosMaxRetailReceipts DB: " + ConversionConfig.CONVERSION_DB_RECEIPTS_NAME;
            //LotsSupplierItems = GetSupplierItemCount(LotsConnectionStr);
            CPIAMSuppliers = GetCPIAMSuppliers(CpiamPosMaxRetailStr);
        }

        private static PropertyChangedEventArgs lotsSupplierItemsChangeArgs = new PropertyChangedEventArgs("LotsSupplierItems");
        private List<SupplierItemCountMap> lotsSupplierItems;
        public List<SupplierItemCountMap> LotsSupplierItems
        {
            get
            {
                return lotsSupplierItems;
            }
            set
            {
                lotsSupplierItems = value;
                if (PropertyChanged != null)
                    PropertyChanged(this, lotsSupplierItemsChangeArgs);
            }
        }

        private static PropertyChangedEventArgs cpiamSuppliersChangeArgs = new PropertyChangedEventArgs("CPIAMSuppliers");
        private List<CPIAMSupplier> cpiamSuppliers;
        public List<CPIAMSupplier> CPIAMSuppliers
        {
            get
            {
                return cpiamSuppliers;
            }
            set
            {
                cpiamSuppliers = value;
                if (PropertyChanged != null)
                    PropertyChanged(this, cpiamSuppliersChangeArgs);
            }
        }

        public List<SupplierItemCountMap> GetSupplierItemCount(String LotsConnectionString)
        {
            List<SupplierItemCountMap> supplierItemCounts = new List<SupplierItemCountMap>();
            OleDbConnection dbConn = new OleDbConnection(LotsConnectionString);
            try
            {
                dbConn.Open();
                using (OleDbCommand command = dbConn.CreateCommand())
                {
                    command.CommandText = string.Format(@"SELECT PartCode.SupplierID, Supplier.SupplierName, Count(PartCode.StockID) as itemcount FROM PartCode,Supplier where Supplier.SupplierId=PartCode.SupplierID  GROUP BY PartCode.SupplierID, Supplier.SupplierName");

                    OleDbDataReader reader = command.ExecuteReader();

                    while (reader.Read())
                    {
                            int supplierID = reader.GetInt32(0);
                            String supplierName = reader.IsDBNull(1) ? null : reader.GetString(1);
                            int itemCount = reader.GetInt32(2);
                            if (itemCount > 0)
                            {
                                SupplierItemCountMap supplierItemCount = new SupplierItemCountMap();
                                supplierItemCount.LotsSupplierID = supplierID;
                                supplierItemCount.LotsSupplierName = supplierName;
                                supplierItemCount.LotsItemCount = itemCount;
                                supplierItemCounts.Add(supplierItemCount);
                            }
                    }
                }
            }
            catch (Exception ex)
            {
                throw ex;
            }
            finally
            {
                dbConn.Close();
            }

            return supplierItemCounts.OrderByDescending(s => s.LotsItemCount).ToList();
        }

        public static List<CPIAMSupplier> GetCPIAMSuppliers(String connectionString)
        {
            List<CPIAMSupplier> suppliers = new List<CPIAMSupplier>();
            CPIAMSupplier emptySupplier = new CPIAMSupplier();
            emptySupplier.SupplierName = null;
            suppliers.Add(emptySupplier);

            String query = string.Format(@"select SupplierNo, SupplierID, SupplierName from suppliers order by SupplierName");
            SqlConnection conn = null;
            SqlDataReader reader = null;

            try
            {
                conn = new SqlConnection(connectionString);
                conn.Open();

                SqlCommand command = new SqlCommand(query, conn);
                reader = command.ExecuteReader();

                while (reader.Read())
                {
                    CPIAMSupplier supplier = new CPIAMSupplier();
                    supplier.SupplierNo = reader.GetGuid(0);
                    supplier.SupplierID = reader.GetInt32(1);
                    supplier.SupplierName = reader.GetString(2);

                    suppliers.Add(supplier);
                }
            }
            catch (Exception)
            {
                return null;
            }
            finally
            {
                if (reader != null)
                    reader.Close();

                if (conn != null)
                    conn.Close();
            }

            return suppliers;
        }

        private void Convert_Click(object sender, RoutedEventArgs e)
        {
            if(LotsFile.Content.ToString()=="")
            {
                MessageBox.Show("Select Lots Database!");
                return;
            }

            DateTime start = DateTime.Now;
            List<SupplierItemCountMap> suppliersMapped = LotsSupplierItems.Where(q => !Object.Equals(q.CPIAMSupplier, null) && q.CPIAMSupplier.SupplierNo != Guid.Empty).ToList();
            if (suppliersMapped.Count == 0)
            {
                MessageBoxResult result = MessageBox.Show("No Suppliers Have been Mapped\nDo you want to continue?", "No Suppliers", MessageBoxButton.YesNo, MessageBoxImage.Question);
                if (result != MessageBoxResult.Yes)
                    return;
            }

            Dictionary<int, Guid> clerkIDMappings = StaffConverter.ConvertStaff(LotsConnectionStr, CpiamPosMaxRetailStr);
            Dictionary<int, string> categoryIDToNameMap = ProductClassConverter.ConvertProductClass(LotsConnectionStr, CpiamPosMaxRetailStr);
            Dictionary<int, int> LotsDepartmentReallocations = ProductGroupConverter.ConvertProductGroup(LotsConnectionStr, CpiamPosMaxRetailStr);
            AccountClassConverter.ConvertAccountClass(LotsConnectionStr, CpiamPosMaxRetailStr);
            AgenciesConverter.ConvertAgencies(LotsConnectionStr, CpiamPosMaxRetailStr);
            DeptsConverter.ConvertDepts(LotsConnectionStr, CpiamPosMaxRetailStr);
            ManufsConverter.ConvertManufs(LotsConnectionStr, CpiamPosMaxRetailStr);
            Dictionary<int, Tuple<int, String>> LotsSupplierReallocations = SuppliersConverter.ConvertSuppliers(LotsConnectionStr, CpiamPosMaxRetailStr, suppliersMapped, CPIAMSuppliers);
            Dictionary<int, StockFileDetail> LotsItemDetails = StockConverter.ConvertStockFile(LotsConnectionStr, CpiamPosMaxRetailStr, suppliersMapped, LotsSupplierReallocations, LotsDepartmentReallocations, categoryIDToNameMap);
            //SalesHistoryConverter.ConvertSalesHistory(LotsConnectionStr, CpiamPosMaxRetailStr);
            //PurchHistoryConverter.ConvertPurchHistoryConverter(LotsConnectionStr, CpiamPosMaxRetailStr);
            
            Dictionary<int, DebtorHeaderDetail> LotsCustomerIDToCPIAMDebtorHeader = PersonsDebtorsConverter.ConvertPersonsDebtors(LotsConnectionStr, CpiamPosMaxRetailStr);
            PersonsLaybysConverter.ConvertPersonsLaybys(LotsConnectionStr, CpiamPosMaxRetailStr);
            Dictionary<int, Guid> transactionNumberToDebtorHeaderID;
            //Dictionary<int, Guid> transactionNumberToDebtorHeaderID=new Dictionary<int,Guid>();
            //Dictionary<int, Guid> clerkIDMappings=new Dictionary<int,Guid>();
            //Dictionary<int, StockFileDetail> LotsItemDetails = new Dictionary<int, StockFileDetail>();
            //Dictionary<int, DebtorHeaderDetail> LotsCustomerIDToCPIAMDebtorHeader = new Dictionary<int, DebtorHeaderDetail>();
            Dictionary<int, TransactionDetail> LotsTransactionDetails = RegisterConverter.ConvertRegister(LotsConnectionStr, CpiamPosMaxRetailReceiptsStr, LotsCustomerIDToCPIAMDebtorHeader, clerkIDMappings, out transactionNumberToDebtorHeaderID);
            RegisterTransactionsConverter.ConvertRegisterTransactions(LotsConnectionStr, CpiamPosMaxRetailReceiptsStr, LotsItemDetails, LotsTransactionDetails, transactionNumberToDebtorHeaderID);
            DateTime end = DateTime.Now;
            MessageBox.Show("Total Time: " + (end - start).ToString());
            
        }

        #region IProgressListener methods
        private static PropertyChangedEventArgs statusStringChangeArgs = new PropertyChangedEventArgs("StatusString");
        private string statusString;
        public String StatusString
        {
            get
            {
                return statusString;
            }
            set
            {
                statusString = value;
                if (PropertyChanged != null)
                    PropertyChanged(this, statusStringChangeArgs);
            }
        }

        private static PropertyChangedEventArgs maxValueChangeArgs = new PropertyChangedEventArgs("MaxValue");
        private double maxValue;
        public double MaxValue
        {
            get { return maxValue; }
            set
            {
                maxValue = value;
                if (PropertyChanged != null)
                    PropertyChanged(this, maxValueChangeArgs);
            }
        }

        private static PropertyChangedEventArgs minValueChangeArgs = new PropertyChangedEventArgs("MinValue");
        private double minValue;
        public double MinValue
        {
            get { return minValue; }
            set
            {
                minValue = value;
                if (PropertyChanged != null)
                    PropertyChanged(this, minValueChangeArgs);
            }
        }

        private static PropertyChangedEventArgs progressValueChangeArgs = new PropertyChangedEventArgs("ProgressValue");
        private double progressValue;
        public double ProgressValue
        {
            get { return progressValue; }
            set
            {
                progressValue = value;
                if (PropertyChanged != null)
                    PropertyChanged(this, progressValueChangeArgs);
            }
        }

        private static PropertyChangedEventArgs errorCountStringChangeArgs = new PropertyChangedEventArgs("ErrorCountString");
        private string errorCountString;
        public String ErrorCountString
        {
            get
            {
                return errorCountString;
            }
            set
            {
                errorCountString = value;
                if (PropertyChanged != null)
                    PropertyChanged(this, errorCountStringChangeArgs);
            }
        }

        public void SetErrorCount(int errorCount)
        {
            ErrorCountString = String.Format("(Records with Errors: {0})", errorCount);
        }

        public void SetStatusString(string s)
        {
            StatusString = s;
        }

        public void SetMaxValue(double value)
        {
            MaxValue = value;
        }

        public void SetMinValue(double value)
        {
            MinValue = value;
        }

        public void SetProgressValue(double value)
        {
            ProgressValue = value;
        }

        private static PropertyChangedEventArgs runningChangeArgs = new PropertyChangedEventArgs("Running");
        private bool running;
        public bool Running
        {
            get
            {
                return running;
            }

            set
            {
                running = value;
                if (PropertyChanged != null)
                    PropertyChanged(this, runningChangeArgs);
            }
        }

        private bool cancelled=false;
        public bool IsCancelled()
        {
            return cancelled;
        }

        #endregion

        public event PropertyChangedEventHandler PropertyChanged;

        private void OpenDB_Click(object sender, RoutedEventArgs e)
        {
            Microsoft.Win32.OpenFileDialog dlg = new Microsoft.Win32.OpenFileDialog();
            dlg.FileName = "lots.mdb"; // Default file name 
            dlg.DefaultExt = ".mdb"; // Default file extension 
            dlg.Filter = "Access Database File (.mdb)|*.mdb"; // Filter files by extension 

            // Show open file dialog box 
            Nullable<bool> result = dlg.ShowDialog();

            // Process open file dialog box results 
            if (result == true)
            {
                // Open document 
                string filename = dlg.FileName;
                LotsFile.Content = dlg.FileName;
                LotsConnectionStr = @"Provider=Microsoft.Jet.OLEDB.4.0;Data Source=" + filename;
                LotsSupplierItems = GetSupplierItemCount(LotsConnectionStr);
                LotsList.ItemsSource = LotsSupplierItems;
            }
        }

        private void ListView_SelectionChanged(object sender, SelectionChangedEventArgs e)
        {
        }


    }

    public class SupplierItemCountMap : INotifyPropertyChanged
    {
        private int lotsSupplierID;
        public int LotsSupplierID
        {
            get
            {
                return lotsSupplierID;
            }
            set
            {
                lotsSupplierID = value;
                NotifyPropertyChanged("LotsSupplierID");
            }
        }

        private String lotsSupplierName;
        public String LotsSupplierName
        {
            get
            {
                return lotsSupplierName;
            }
            set
            {
                lotsSupplierName = value;
                NotifyPropertyChanged("LotsSupplierName");
            }
        }

        private int lotsItemCount;
        public int LotsItemCount
        {
            get
            {
                return lotsItemCount;
            }
            set
            {
                lotsItemCount = value;
                NotifyPropertyChanged("LotsItemCount");
            }
        }

        private CPIAMSupplier cpiamSupplier;
        public CPIAMSupplier CPIAMSupplier
        {
            get
            {
                return cpiamSupplier;
            }
            set
            {
                cpiamSupplier = value;
                NotifyPropertyChanged("CPIAMSupplier");
            }
        }

        public event PropertyChangedEventHandler PropertyChanged;
        private void NotifyPropertyChanged(String info)
        {
            if (PropertyChanged != null)
            {
                PropertyChanged(this, new PropertyChangedEventArgs(info));
            }
        }
    }

    public class CPIAMSupplier : INotifyPropertyChanged
    {
        private Guid supplierNo;
        public Guid SupplierNo
        {
            get
            {
                return supplierNo;
            }
            set
            {
                supplierNo = value;
                NotifyPropertyChanged("SupplierNo");
            }
        }

        private int supplierID;
        public int SupplierID
        {
            get
            {
                return supplierID;
            }
            set
            {
                supplierID = value;
                NotifyPropertyChanged("SupplierID");
            }
        }

        private string supplierName;
        public string SupplierName
        {
            get
            {
                return supplierName;
            }
            set
            {
                supplierName = value;
                NotifyPropertyChanged("SupplierName");
            }
        }

        public event PropertyChangedEventHandler PropertyChanged;
        private void NotifyPropertyChanged(String info)
        {
            if (PropertyChanged != null)
            {
                PropertyChanged(this, new PropertyChangedEventArgs(info));
            }
        }
    }
}
